﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO;

namespace DbSharp.Framework.TestEngine
{
    public class TestCaseStatusNotifyEventArgs : EventArgs
    {
        public string ErrorMessage { get; set; }
        public CaseRunPhase TestPhase { get; set; }
        public TestRunnerBase TestRunner { get; set; }

        public override string ToString()
        {
            string messageFmt = "in {0} phase at {1}";
            string message = string.Format(messageFmt, TestPhase.ToString(), DateTime.Now.ToLongTimeString());
            if (string.IsNullOrEmpty(ErrorMessage) == false)
                message = message + ", " + ErrorMessage;

            //if it is at the Finished phase, that means we need to provide more message to tell to the user. 
            if (TestPhase == CaseRunPhase.Finished) 
            {
                string failedFooterFmt = 
@"**{0} result: {1}
-----------------------";
                message = message + Environment.NewLine + string.Format(failedFooterFmt, TestRunner.CaseName, TestRunner.CaseExecuteResult.TestState.ToString());
            }
            return message;
        }
    }

    public interface ITestCaseStatusNotify : IDisposable
    {
        TestRunnerBase TestRunner { get; set; }
        void UpdateStatus(TestCaseStatusNotifyEventArgs arg);
    }

    public abstract class TextBasedTestStatusNotifier
        : ITestCaseStatusNotify
    {

        protected readonly TextWriter m_writer;

        #region Ctors

        protected TextBasedTestStatusNotifier(TextWriter writer)
        {
            m_writer = writer;
        }

        #endregion

        #region ITestStatusNotify Members

        public TestRunnerBase TestRunner { get; set; }

   

        public void UpdateStatus(TestCaseStatusNotifyEventArgs arg)
        {
            if (arg == null)
                return;
            string messageFmt = "{0}: {1}";
            string message = string.Format(messageFmt, TestRunner.CaseName, arg.ToString());
            m_writer.WriteLine(message);
        }

        #endregion

        #region IDisposable Members

        void IDisposable.Dispose()
        {
            Dispose(true);
            GC.SuppressFinalize(this);
        }

        protected virtual void Dispose(bool disposing)
        {
            if (disposing)
            {
                m_writer.Dispose();
            }
        }

        ~TextBasedTestStatusNotifier()
        {
            Dispose(false);
        }

        #endregion

    }

    public class ConsoleTestStatusNotifier
        : TextBasedTestStatusNotifier
    {

        public ConsoleTestStatusNotifier()
            : base(Console.Out) { }

        protected override void Dispose(bool disposing) { }

    }
 
   
}
